package com.iteaj.iot.test.client.fixed;

import cn.hutool.core.util.RandomUtil;
import com.iteaj.iot.Message;
import com.iteaj.iot.client.ClientConnectProperties;
import com.iteaj.iot.client.ClientProtocolHandle;
import com.iteaj.iot.client.IotClient;
import com.iteaj.iot.client.IotClientBootstrap;
import com.iteaj.iot.config.ConnectProperties;
import com.iteaj.iot.consts.ExecStatus;
import com.iteaj.iot.test.IotTestProperties;
import com.iteaj.iot.test.TestConst;
import com.iteaj.iot.test.TestProtocolType;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.InitializingBean;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.scheduling.concurrent.ThreadPoolTaskScheduler;

import java.time.Duration;
import java.time.Instant;
import java.util.Collection;
import java.util.List;

public class FixedLengthRequestHandle implements ClientProtocolHandle<FixedLengthRequestProtocol>, InitializingBean {

    @Autowired
    private ThreadPoolTaskScheduler scheduler;
    @Autowired
    private FixedLengthClientComponent component;
    private Logger logger = LoggerFactory.getLogger(getClass());

    @Override
    public Object handle(FixedLengthRequestProtocol protocol) {
        Message.MessageHead head = protocol.requestMessage().getHead();
        String equipCode = head.getEquipCode();
        String desc = "客户端测试";

        if(protocol.getExecStatus() == ExecStatus.success) {
            // 上线数量是值有发送过报文的客户端数量
            logger.info(TestConst.LOGGER_PROTOCOL_DESC+" - 上线数量：{}", component.getName()
                    , desc, equipCode, head.getMessageId(), "通过", protocol.getClientNum());
        } else {
            logger.warn(TestConst.LOGGER_PROTOCOL_DESC, component.getName()
                    , desc, equipCode, head.getMessageId(), "不通过(" + protocol.getExecStatus().desc + ")");
        }
        return null;
    }

    @Override
    public void afterPropertiesSet() throws Exception {
        scheduler.schedule(() -> {
            ConnectProperties config = component.getConfig();
            if(config instanceof IotTestProperties.TestConnectConfig) {
                int clientNum = ((IotTestProperties.TestConnectConfig) config).getNum();
                if(clientNum > 0) {
                    int spiltNum = 1000;
                    do {
                        if(clientNum > spiltNum) {
                            clientNum = clientNum - spiltNum;
                        } else {
                            spiltNum = clientNum;
                            clientNum = 0;
                        }
                        for(int i=0; i< spiltNum; i++) {
                            ClientConnectProperties properties = new ClientConnectProperties();
                            BeanUtils.copyProperties(config, properties);
                            component.createNewClientAndConnect(properties);
                        }
                        try {
                            Thread.sleep(RandomUtil.randomInt(1000, 3000));
                        } catch (InterruptedException e) {
                            e.printStackTrace();
                        }
                    } while (clientNum != 0);
                }
            }
        }, Instant.now().plusSeconds(20));

        scheduler.scheduleAtFixedRate(() -> {
            List<IotClient> clients = component.clients();

            int i = RandomUtil.randomInt(0, clients.size());
            FixedLengthClient client = (FixedLengthClient) clients.get(i);
            FixedLengthClientMessage build = FixedLengthClientMessage.build(client.getDeviceSn(), TestProtocolType.CIReq);
            new FixedLengthRequestProtocol(build).request(client.getConfig());
        }, Instant.now().plusSeconds(32), Duration.ofSeconds(3));
    }
}
